home *** CD-ROM | disk | FTP | other *** search
/ Atari Mega Archive 1 / Atari Mega Archive - Volume 1.iso / telecomm / xprogs.arc / XDOWN.C < prev    next >
C/C++ Source or Header  |  1988-01-05  |  3KB  |  178 lines

  1. /* xdown.c    Xmodem download program */
  2.  
  3. #include <bios.h>
  4. #include <osbind.h>
  5. #include <xbios.h>
  6.  
  7. #define Auxis() Bconstat(BC_AUX)
  8. #define Auxos() Bcostat(BC_AUX)
  9. #define Auxin() ((unsigned char) Bconin(BC_AUX))
  10. #define Auxout(c) Bconout(BC_AUX,c)
  11.  
  12. #define SOH 0x01
  13. #define EOT 0x04
  14. #define ACK 0x06
  15. #define NAK 0x15
  16. #define CAN 0x18
  17.  
  18. #define NULL (char *)0
  19. #define SIZE 128
  20. #define FALSE 0
  21. #define TRUE 1
  22.  
  23. extern    char    *itoa();
  24.  
  25. unsigned char    get_char();
  26.     char    packet[SIZE+1];
  27.  
  28. main(argc,argv)
  29.     int    argc;
  30.     char    *argv[];
  31. {
  32.     char    *name;
  33.     int    fp,bw,ec,n;
  34. unsigned int    packets,xpackets,oldxpackets;
  35. unsigned char    chr,packet_num,packet_xnum,checksum;
  36.  
  37.     if (argc<2 || argc>3)
  38.         fatal("Usage: xdown file [errors]");
  39.     name=argv[1];
  40.     ec=10;
  41.     if (argc==3)
  42.         if ((ec=atoi(argv[2]))<1)
  43.             fatal("Illegal error count value");
  44.     Cconws("\r\nxdown v1.0 by Jason Blochowiak\r\n");
  45.     if ((fp=creat(name,1))==-1)
  46.         fatal("Unable to create target file.");
  47.  
  48.     send_char(NAK);
  49.     oldxpackets=0xFFFF;
  50.     for (packets=1;;)
  51.     {
  52.         Cconws("\rR#");
  53.         Cconws(itoa(packets));
  54.         Cconws(" (");
  55.         Cconws(itoa(ec));
  56.         Cconws(" errs left)");
  57.         xpackets=packets & 0xFF;
  58.         if ((chr=get_char(10))==EOT)
  59.         {
  60.             send_char(ACK);
  61.             break;
  62.         };
  63.         if (chr==CAN)
  64.             fatal("Transmission aborted remotely");
  65.         if
  66.         (
  67.                chr!=SOH
  68.             || ((packet_num=get_char(1))==-1)
  69.             || ((packet_num!=xpackets)&&(packet_num!=oldxpackets))
  70.             || ((packet_xnum=get_char(1))==-1)
  71.             || ((packet_xnum ^ 0xFF)!=packet_num)
  72.             || ((n=read_packet(SIZE,&checksum))!=SIZE)
  73.             || (checksum!=0)
  74.         )
  75.         {
  76.             if (chr!=SOH)
  77.                 prerror("Not SOH");
  78.             else if ((packet_xnum ^ 0xFF)!=packet_num)
  79.                 prerror("Unmatching packet #s");
  80.             else if (checksum!=0)
  81.                 prerror("Non-zero checksum value.");
  82.             else if (n!=SIZE)
  83.                 prerror("Incomplete packet.");
  84.             send_char(NAK);
  85.             if (ec--==0)
  86.                 fatal("Too many errors");
  87.         }
  88.         else
  89.         {
  90.             send_char(ACK);
  91.             if (xpackets==packet_num)
  92.             {
  93.                 oldxpackets=xpackets;
  94.                 packets++;
  95.             }
  96.             else if (oldxpackets==packet_num)
  97.                 lseek(fp,(long) (packets-1)*128,0);
  98.  
  99.             if ((bw=write(fp,packet,SIZE))<SIZE)
  100.                 fatal("Unable to write to file.");
  101.         }
  102.     }
  103.     if (close(fp)==-1)
  104.         fatal("Unable to close file.");
  105.     Cconws("xdown: successful recieve of");
  106.     Cconws(itoa(packets));
  107.     Cconws(" packets.\r\n");
  108.     Cconin();
  109.     exit(0);
  110. }
  111.  
  112.  
  113. fatal(s)
  114.     char    *s;
  115. {
  116.     Cconws("\r\nxdown: ");
  117.     Cconws(s);
  118.     Cconws(".\a");
  119.     Cconin();
  120.     exit(1);
  121. }
  122.  
  123. prerror(s)
  124.     char    *s;
  125. {
  126.     Cconws("\r\n");
  127.     Cconws(s);
  128.     Cconws("\a\r\n");
  129. }
  130.  
  131. read_packet(size,check)
  132. unsigned int    size;
  133. unsigned char    *check;
  134. {
  135. register int    i;
  136. unsigned char    cs;
  137.  
  138.     i=0;
  139.     while ( (i<size) && ((packet[i]=get_char(1))!=-1) )
  140.         cs=0xFF & (cs+=packet[i++]);
  141.     *check=cs ^ get_char(1);
  142.     return(i);
  143. }
  144.  
  145.  
  146. in_status()
  147. {
  148.     if (Auxis())
  149.         return(0);
  150.     else
  151.         return(1);
  152. }
  153.  
  154. unsigned char    get_char(wait)
  155.     int    wait;
  156. {
  157. register int    i;
  158.  
  159.     for (i=0;i<wait*60;i++)
  160.         if (in_status())
  161.             Vsync();
  162.         else
  163.             return(Auxin()&0xff);
  164.     return(-1);
  165. }
  166.  
  167. send_char(chr)
  168. unsigned char    chr;
  169. {
  170.     flush();
  171.     Auxout(chr);
  172. }
  173.  
  174. flush()
  175. {
  176.     while (get_char(1)!=-1);
  177. }
  178.